home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
FM Towns: Free Software Collection 4
/
FM Towns Free Software Collection 4 - Disc 1.iso
/
toda
/
src
/
quad.c
< prev
next >
Wrap
Text File
|
1991-10-18
|
14KB
|
538 lines
/* quad expand for video recordre 1990 6/8
*/
#include <stdlib.h>
#include <math.h>
#include <egb.h>
#include <mos.h>
#include "video.h"
#define C_WT 0x7fff /* カーソル color */
#define C_B 0x3ff /* box color */
#define C_PL 24311 /* 初期プレーン color */
#define C_FL 0x303030 /* files back color */
#define C_COLOR 15 /* Command color palette */
#define W_COLOR 8 /* Window color palette */
#define B_COLOR 7 /* Back color palette */
#define E_COLOR 10 /* ERROR color palette */
#define S1_COLOR 4 /* SCALE1 color palette */
#define S2_COLOR 12 /* SCALE2 color palette */
extern error_check( int n );
extern mouse( int para[], int xd, int yd, int mode );
extern gprint( char *dsp, int x, int y );
extern gprint2( char *dsp, int x, int y );
extern itochar( int number, int x, char *dsp );
extern windget();
extern windput();
/* extern mov_save_trim( int var[], int color ); */
extern mov_save_page( char *name, int mode, int var[] );
extern display_scale();
extern polygon1( int para[], char *bbuf );
extern polygon2( char *bbuf );
extern polygon3( char *bbuf );
quad_expand(pvar,cvar,ework,gwork,bbuf)
int pvar[]; /* page */
int cvar[][2]; /* 座標 */
char *ework, *gwork, *bbuf;
{
int min,max,i,j,k,wt,sw,cx,cy,polysw,mode;
int mp[3];
int pp[5];
int data[2];
char dsp1[] = "<<EXPAND>> SOURCE-RECTANGLE START-QUADRANGLE END-QUADRANGLE PAGE= EXIT";
char dsp2[] = "REC1 REC2 EXPAND(page ) CANCEL POLYGON-SET POLYGON-OFF TRACE";
backupget(bbuf,gwork); /* 全画面保存 */
polysw = pvar[4];
if( polysw )polygon2(bbuf);
quad1: windget();
gprint( dsp1, 0, 463 );
gprint( dsp2, 0, 479 );
EGB_color(ework,0,E_COLOR);
gprint( "REC1 REC2", 0, 479 );
EGB_color(ework,0,C_COLOR);
for( i = 0 ; i < 2 ; i++ )data[i] = -1;
quad_dsp(data,pvar);
quad2: MOS_disp(1);
mouse( mp, 0, 0, 1 );
sw = mp[0]; cx = mp[1]; cy = mp[2];
if( cy < 447 )goto quad2;
if( cy < 463 ){
if( cx < 88 )goto quad2;
if( cx < 232 ){ /* source 0 */
j = 0;
goto quad3;
}
if( cx < 376 ){ /* start_quad 1 */
j = 1;
goto quad3;
}
if( cx < 504 ){ /* end_quad 2 */
j = 2;
goto quad3;
}
if( cx < 584 ){ /* page */
i = 0; min = 2; max = 999;
goto quad7;
}
if( cx < 600 )goto quad2;
if( cx < 640 ){ /* exit 3 */
j = 3;
goto quad3;
}
goto quad2;
}
if( cy < 480 ){
if( cx < 40 ){ /* rec1 */
mode = 0;
j = 9;
goto quad3;
}
if( cx < 88 ){ /* rec2 */
mode = 1;
j = 9;
goto quad3;
}
if( cx < 148 ){ /* expand 4 */
j = 4;
goto quad3;
}
if( cx < 232 ){ /* page */
i = 1; min = 1; max = pvar[0];
goto quad7;
}
if( cx < 296 ){ /* cancel 5 */
j = 5;
goto quad3;
}
if( cx < 376 )goto quad2;
if( cx < 480 ){ /* POLYGON-SET 6 */
j = 6;
goto quad3;
}
if( cx < 584 ){ /* POLYGON-OFF 7 */
j = 7;
goto quad3;
}
if( cx < 592 )goto quad2;
if( cx < 640 ){ /* trace 8 */
j = 8;
goto quad3;
}
goto quad2;
}
goto quad2;
quad3: mouse(mp, 0, 0, 0);
sw = mp[0]; cx = mp[1]; cy = mp[2];
if( sw > 1 )goto quad2;
MOS_disp(0);
windput();
switch( j ){
case 0: rectangle_coodr( cvar,ework ); /* rectangole */
break;
case 1: sourcebox_display(cvar,ework);
quad_coodr( cvar, 2, ework ); /* start quad */
sourcebox_display(cvar,ework);
break;
case 2: sourcebox_display(cvar,ework);
quad_coodr( cvar, 6, ework ); /* end quad */
sourcebox_display(cvar,ework);
break;
case 3: polygon2( bbuf );
return 0; /* exit */
case 4: polygon2( bbuf ); /* expand */
error_check(
expand_copy(pvar,cvar,polysw,bbuf,ework,gwork)
);
polygon2( bbuf );
break;
case 5: polygon2( bbuf );
backupput( bbuf, gwork ); /* cancel */
polygon2( bbuf );
break;
case 6: polygon2( bbuf );
sourcebox_display(cvar,ework);
polysw = 1;
if( polygon1( pp, bbuf ) )polysw = 0; /* polygon */
sourcebox_display(cvar,ework);
break;
case 7: polygon2( bbuf ); /* polygon-off */
polygon3( bbuf );
polysw = 0;
break;
case 8: sourcebox_display(cvar,ework);
quad_check( pvar[0], cvar, ework ); /* trace */
sourcebox_display(cvar,ework);
break;
case 9: polygon2( bbuf );
if(
error_check(
mov_save_page(
(char *)pvar[5], mode, (int *)pvar[3]
)
)
){
polygon3( bbuf );
return -1;
}
polygon2( bbuf );
break; /* rec */
}
goto quad1;
quad7: wt = 125000;
quad8: if( sw == 1 )pvar[i] = pvar[i] + 1;
if( sw == 2 )pvar[i] = pvar[i] - 1;
if( pvar[i] < min )pvar[i] = max;
if( pvar[i] > max )pvar[i] = min;
quad_dsp(data,pvar);
for( k = 0 ; k < wt ; k++ );
wt = 10000;
MOS_rdpos(&sw,&cx,&cy);
if( sw > 0 )goto quad8;
goto quad2;
}
quad_dsp(data,var)
int data[],var[];
{
int i, x, y;
int point[][3] = { { 552,463,3 },
{ 192,479,3 }
};
char dsp[10];
for( i = 0 ; i < 2 ; i++ ){
if( data[i] != var[i] ){
x = point[i][0]; y = point[i][1];
MOS_disp(0);
itochar( var[i], point[i][2], dsp );
gprint2( dsp, x, y );
data[i] = var[i];
}
}
return 0;
}
backupget(bbuf,gwork) /* 保存 */
char *bbuf,*gwork;
{
char para[8];
DWORD(para+0) = (unsigned int)bbuf;
DWORD(para+4) = 0x104;
geta17(gwork,para); /* polygon data 保存 1991 2/28 */
return 0;
}
backupput(bbuf,gwork) /* 画面バック(cancel) */
char *bbuf,*gwork;
{
char para[12];
DWORD(para+0) = (unsigned int)bbuf;
DWORD(para+4) = 0x104;
DWORD(para+8) = 12; /* 1991 2/28 特設 */
puta17(gwork,para);
return 0;
}
sourcebox_display(var,ework)
int var[][2];
char *ework;
{
char para[8];
EGB_writePage(ework,0); /* mode10に書き込み */
EGB_color(ework,0,C_B);
EGB_paintMode(ework,0x2);
EGB_writeMode(ework,4);
WORD(para + 0) = var[0][0];
WORD(para + 2) = var[0][1];
WORD(para + 4) = var[1][0];
WORD(para + 6) = var[1][1];
EGB_rectangle(ework,para);
return 0;
}
rectangle_coodr( var, ework )
int var[][2];
char *ework;
{
int sw, cx, cy, temp;
int v[2][2], mp[3];
display_scale();
EGB_writePage(ework,0); /* mode10に書き込み */
MOS_horizon(0,319);
MOS_vertical(0,239);
MOS_setpos( 160, 120 );
MOS_disp(0);
cood1: mouse(mp,0,0,10);
sw = mp[0]; cx = mp[1]; cy = mp[2];
if( sw > 1 )goto cood3;
v[0][0] = cx; v[0][1] = cy;
mouse(mp,0,0,4);
sw = mp[0]; cx = mp[1]; cy = mp[2];
if( sw > 1 )goto cood1;
if( cx == v[0][0] || cy == v[0][1] )goto cood3;
v[1][0] = cx; v[1][1] = cy;
if( v[0][0] > v[1][0] ){ /* 大小整頓 */
temp = v[0][0];
v[0][0] = v[1][0];
v[1][0] = temp;
}
if( v[0][1] > v[1][1] ){
temp = v[0][1];
v[0][1] = v[1][1];
v[1][1] = temp;
}
var[0][0]=v[0][0]; var[0][1]=v[0][1];
var[1][0]=v[1][0]; var[1][1]=v[1][1];
cood3: EGB_writePage(ework,1); /* mode3に書き込み */
MOS_horizon(0,639);
MOS_vertical(0,479);
MOS_setpos( 320, 240 );
return 0;
}
quad_coodr( var, n, ework )
int var[][2],n;
char *ework;
{
int sw, cx, cy, i, bn;
int mp[3];
int b[6][2];
display_scale();
EGB_writePage(ework,0); /* mode10に書き込み */
MOS_horizon(0,319);
MOS_vertical(0,239);
MOS_setpos( 160, 120 );
MOS_disp(0);
cood1: mouse( mp, 0, 0, 10 );
sw = mp[0]; cx = mp[1]; cy = mp[2];
if( sw > 1 )goto cood2;
bn = 0; b[0][0] = cx; b[0][1] = cy;
while( bn < 3 ){
mouse( mp, 0, 0, 2 );
sw = mp[0]; cx = mp[1]; cy = mp[2];
if( sw > 1 ){
if( bn == 0 )goto cood1;
for( i=1 ; i<=bn ; i++ ){ /* やりなおし */
line_set(
b[i-1][0], b[i-1][1], b[i][0], b[i][1], ework
);
}
goto cood1;
}
bn++; b[bn][0] = cx; b[bn][1] = cy; /* 次のステップ */
line_set( b[bn-1][0], b[bn-1][1], b[bn][0], b[bn][1], ework );
}
bn = 4; b[4][0] = b[0][0]; b[4][1] = b[0][1]; /* 最後のライン */
line_set( b[3][0], b[3][1], b[4][0], b[4][1], ework );
for( i=1 ; i<=bn ; i++ ){ /* ライン消し */
line_set( b[i-1][0], b[i-1][1], b[i][0], b[i][1], ework );
}
if( error_check( square_check( b ) ) )goto cood2;
for( i=0 ; i<4 ; i++ ){
var[i+n][0] = b[i][0];
var[i+n][1] = b[i][1];
}
cood2: EGB_writePage(ework,1); /* mode3に書き込み */
MOS_horizon(0,639);
MOS_vertical(0,479);
MOS_setpos( 320, 240 );
return 0;
}
quad_check( n, var, ework )
int n, var[][2];
char *ework;
{
int i, j, mp[3], outvar[5][2];
for( i=0 ; i<10 ; i++ ){
if( var[i][0] < 0 ){ /* data check */
error_check( 4 );
return -1;
}
}
EGB_writePage(ework,0); /* mode10に書き込み */
for( j=0 ; j<2 ; j++ ){
if( j )mouse( mp, 0, 0, 0 );
for( i=1 ; i<=n ; i++ ){
quad_out( i, outvar, n, var );
quad_line( outvar, ework );
}
}
EGB_writePage(ework,1); /* mode3に書き込み */
return 0;
}
expand_copy( pvar, var, polysw, bbuf, ework, gwork )
int pvar[], var[][2], polysw;
char *bbuf, *ework, *gwork;
{
int p, n, col; /* page1 page0 color */
int ax1, ay1, ax2, ay2;
int temp, i, xmin, ymin, xmax, ymax, ax, ay, axm, aym, det;
int bx0, by0, bx1, by1, bx2, by2, bx3, by3;
int b[6][2], para[18];
char para2[8];
p = pvar[1]; n = pvar[0]; col = pvar[2];
if( p > n )return 54; /* error check */
if( var[0][0] >= var[1][0] )return 4;
if( var[0][1] >= var[1][1] )return 4;
for( i=2 ; i<10 ; i++ ){
if( var[i][0] < 0 )return 4;
}
EGB_writePage(ework,0); /* mode10に書き込み */
EGB_color(ework,0,col); /* paint color set */
EGB_color(ework,2,col);
EGB_paintMode(ework,0x22);
EGB_writeMode(ework,0);
EGB_penSize(ework,1);
WORD(para2 +0 ) = 0;
WORD(para2 +2 ) = 0;
WORD(para2 +4 ) = 319;
WORD(para2 +6 ) = 239;
EGB_rectangle( ework, para2 );
quad_out( p, b, n, var );
if( ( temp = square_check( b ) ) != 0 )goto expnd1;
quad_line( b, ework );
if( polysw == 0 )polygon_box( var, bbuf ); /* polygon */
quad_line( b, ework );
para[0] = (unsigned int)bbuf;
para[1] = 0x104;
ax1 = var[0][0]; ay1 = var[0][1];
ax2 = var[1][0]; ay2 = var[1][1];
xmin = b[0][0]; xmax = b[0][0]; ymin = b[0][1]; ymax = b[0][1];
for( i=0 ; i<4 ; i++ ){ /* 最大,最小 */
if( xmin > b[i][0] )xmin = b[i][0];
if( xmax < b[i][0] )xmax = b[i][0];
if( ymin > b[i][1] )ymin = b[i][1];
if( ymax < b[i][1] )ymax = b[i][1];
}
bx0 = b[0][0]; by0 = b[0][1];
bx1 = b[1][0] - bx0; by1 = b[1][1] - by0;
bx2 = b[2][0] - bx0; by2 = b[2][1] - by0;
bx3 = b[3][0] - bx0; by3 = b[3][1] - by0;
ax = ax2 - ax1; ay = ay2 - ay1;
det = bx1*by3 - bx3*by1;
if( det == 0 ){
temp = 100;
goto expnd1;
}
para[2] = ( ((double)ax)*by3*65536 )/det;
para[3] = -( ((double)ax)*bx3*65536 )/det;
para[4] = -( ((double)ay)*by1*65536 )/det;
para[5] = ( ((double)ay)*bx1*65536 )/det;
axm = para[2]*bx2 + para[3]*by2;
aym = para[4]*bx2 + para[5]*by2;
if( (axm == 0) || (aym == 0) ){
temp = 100; /* axm*aym==0はerror god-transも同じ */
goto expnd1; /* overflow=0になる↑対処せよ91 2・25 */
}
para[6] = ( (double)( axm - ax*65536 ) )/ax/aym*65536;
para[7] = ( (double)( aym - ay*65536 ) )/ay/axm*65536;
para[8] = bx0; para[9] = by0;
para[10] = ax1 * 65536; para[11] = ay1 * 65536;
para[12] = xmin; para[13] = ymin; para[14] = xmax; para[15] = ymax;
para[16] = 256;
expand17( gwork, para );
expnd1: if( polysw == 0 )poly1(bbuf); /* polygon data clear */
EGB_writePage(ework,1); /* mode3に書き込み */
return temp;
}
polygon_box( var, bbuf ) /* box area set */
int var[][2];
char *bbuf;
{
int x1, x2, y, address;
poly1(bbuf); /* polygon data clear */
x1 = var[0][0]; x2 = var[1][0];
for( y=var[0][1] ; y<=var[1][1] ; y++ ){
address = y * 1024 + x1 * 2;
WORD( bbuf + address ) = WORD( bbuf + address ) | 0x8000;
address = y * 1024 + x2 * 2;
WORD( bbuf + address ) = WORD( bbuf + address ) | 0x8000;
}
poly2( bbuf, var[0][1], var[1][1] );
return 0;
}
/* nページ分割 var[2][0]-var[9][2] → pページ出力 outvar[0][0]-outvar[3][2] */
quad_out( p, outvar, n, var )
int p, outvar[5][2], n, var[][2];
{
int i, m, m1, m2;
m = n - 1; m1 = p - 1; m2 = m - m1;
for( i=0 ; i<4 ; i++ ){
outvar[i][0] = ( m2*var[i+2][0] + m1*var[i+6][0] ) / m;
outvar[i][1] = ( m2*var[i+2][1] + m1*var[i+6][1] ) / m;
}
outvar[4][0] = outvar[0][0]; outvar[4][1] = outvar[0][1];
return square_check(outvar); /* 外積チェック */
}
quad_line( var, ework )
int var[5][2];
char *ework;
{
int i;
for( i=1 ; i<=4 ; i++ ){ /* ライン */
line_set( var[i-1][0], var[i-1][1], var[i][0], var[i][1], ework );
}
return 0;
}
line_set( x1, y1, x2, y2, ework )
int x1, y1, x2, y2;
char *ework;
{
char para[32];
EGB_color(ework,0,C_WT);
EGB_writeMode( ework, 4 ); /* XOR */
EGB_paintMode( ework, 0x22 );
WORD( para+0 ) = 2;
WORD( para+2 ) = x1;
WORD( para+4 ) = y1;
WORD( para+6 ) = x2;
WORD( para+8 ) = y2;
EGB_unConnect( ework, para );
return 0;
}
square_check(b) /* 外積チェック */
int b[5][2];
{
int data[4], a[4][2];
a[0][0] = b[1][0] - b[0][0]; /* ベクトル */
a[0][1] = b[1][1] - b[0][1];
a[1][0] = b[2][0] - b[1][0];
a[1][1] = b[2][1] - b[1][1];
a[2][0] = b[3][0] - b[2][0];
a[2][1] = b[3][1] - b[2][1];
a[3][0] = b[0][0] - b[3][0];
a[3][1] = b[0][1] - b[3][1];
data[0] = a[0][0]*a[1][1] - a[0][1]*a[1][0]; /* 外積 */
data[1] = a[1][0]*a[2][1] - a[1][1]*a[2][0];
data[2] = a[2][0]*a[3][1] - a[2][1]*a[3][0];
data[3] = a[3][0]*a[0][1] - a[3][1]*a[0][0];
if( ((double)data[0])*data[1]*data[2]*data[3] > 0 )return 0;
return 100;
}